﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Net.Mail;
using System.Net;
using MongoDB.Bson;
using Outlook = Microsoft.Office.Interop.Outlook;
using lo = sqCore.sqLogger;

namespace sqCore
{
    /* Docs:
     * Summary
        * Mail object for SqlA Server.
        * Allows send mail with SMTPServer or by using OutLook.
     * Variables
        * HTMLParams - Parts of the mail, will set one by one to the mail body message.
        * Recipients - List of recipients mail addresses.
        * From - Sender username.
        * NumberOfCopy - Number of copy to send each recipient
        * AttachmentsPaths - List of paths of files to Attach the mail.
        * MailSubject - Subject for the mail.        
     */
    public class sqMail
    {
        public string[] HTMLParams;
        public string[] Recipients;
        public string From;
        public int NumberOfCopy;
        public string[] AttachmentsPaths;
        public string MailSubject;

        /* Docs:
         * Summary: Initialize the Mail.
         */
        public sqMail(string[] HTMLParams = default(string[]), string[] Recipients = null, 
                string From = "Anonymous", int NumberOfCopy = 1, string[] AttachmentsPaths = null,
                string MailSubject = "This is an automatic message")
        {
            if (Recipients == null)  Recipients = new string[0];
            if (AttachmentsPaths == null) AttachmentsPaths = new string[0];
            this.MailSubject = MailSubject;
            if (HTMLParams == default(string[]))
                HTMLParams =  new string[1]{""};
            this.HTMLParams = HTMLParams;
            this.Recipients = Recipients;
            this.From = From;
            this.NumberOfCopy = NumberOfCopy;
            this.AttachmentsPaths = AttachmentsPaths;
        }

        /* Docs:
         * Summary: Format recipients from string to arry. split by a comma(,)
         * Variables: 
            * Recipients - String of recipients
         */
        public void setRecipientsFromStr(string Recipients)
        {
            this.Recipients = Recipients.Split(',');
        }

        /* Docs:
         * Summary: Send email through SMTP server      
         * Variables:
            * SMTPServerAddress - The address of the SMTP server.
            * SMTPPassword - Password for the UserName account.
         * Exceptions: 
           * ex - Thrown when failed to add the attachments to the mail. can happened paths is incorrect
           * ex2 - Thrown when failed send the mail. can happened if the user/pass incorrect or if the smtp server is not found.
         */
        public void sendThroughSMTP(string SMTPServerAddress = "smtp.gmail.com", string SMTPPassword= "rtuyrnxpe") //TODO //CONFIG
        {
            try
            {
                MailMessage msg = new MailMessage(); //Create new message.
                msg.From = new MailAddress(this.From);
                foreach (string recipient in this.Recipients)
                {
                    msg.To.Add(recipient);
                }
                msg.Subject = this.MailSubject;

                    foreach (string AttachmentsPath in this.AttachmentsPaths)
                    {
                        try
                        {
                            msg.Attachments.Add(new Attachment(@AttachmentsPath)); //Add attachments.
                        }
                        catch (Exception ex)
                        {
                            lo.writeLog(LogMessage: "Failed to add the attachments.", isError: true, Params: new List<string> { ex.ToString(), this.AttachmentsPaths.ToJson() });
                        }
                    }
                

                foreach (string HTMLParams in this.HTMLParams)
                {
                    msg.Body += HTMLParams; //Add html parts to the body.
                    msg.Body += "<br>";
                }
                msg.IsBodyHtml = true;
                //SMTP client
                SmtpClient sC = new SmtpClient(SMTPServerAddress); //Set smtp server.
                sC.Port = 587;
                //credentials to login in to Gmail account
                sC.Credentials = new NetworkCredential(this.From, SMTPPassword); //Check account params.
                sC.EnableSsl = true;
                for (int i = 0; i < this.NumberOfCopy; ++i)
                {
                    sC.Send(msg); //Send the message.
                    lo.writeLog(LogMessage: "Mail sent.", debugOnly:true);
                }
            }
            catch (Exception ex2)
            {
                lo.writeLog(LogMessage: "Failed to send the mail.", isError:true, Params: new List<string> {ex2.ToString(),this.ToJson()});
            }
            
        }

        /* Docs:
         * Summary: Send email through outlook..
         * Exceptions: 
           * ex - Thrown when failed to add the attachments to the mail. can happened paths is incorrect
           * ex2 - Thrown when failed send the mail. can happened if the user/pass incorrect or if the outlook not configured right.
         */
        public void sendThroughOUTLOOK()
        {
            try
            {
                Outlook.Application oApp = new Outlook.Application();
                // Create a new mail item.
                Outlook.MailItem oMsg = (Outlook.MailItem)oApp.CreateItem(Outlook.OlItemType.olMailItem);
                foreach (string HTMLParams in this.HTMLParams)
                {
                    oMsg.HTMLBody += this.HTMLParams;
                    oMsg.HTMLBody += "<br>";
                }
                
                Outlook.Recipients oRecips = (Outlook.Recipients)oMsg.Recipients;
                foreach (string recipient in this.Recipients)
                {
                    Outlook.Recipient oRecip = (Outlook.Recipient)oRecips.Add(recipient);
                    oRecip.Resolve();
                    oRecip = null;
                }
                foreach (string AttachmentsPath in this.AttachmentsPaths)
                {
                    try
                    {
                        int iPosition = (int)oMsg.Body.Length + 1;
                        int iAttachType = (int)Outlook.OlAttachmentType.olByValue;
                        String sDisplayName = "MyAttachment";
                        Outlook.Attachment oAttach = oMsg.Attachments.Add(@AttachmentsPath, iAttachType, iPosition, sDisplayName);
                    }
                    catch (Exception ex)
                    {
                        lo.writeLog(LogMessage: "Failed to add the attachments.", isError: true, Params: new List<string> { ex.ToString(), this.AttachmentsPaths.ToJson() });
                    }
                    
                }
                oMsg.Subject = this.MailSubject;
                // Send.
                for (int i = 0; i < this.NumberOfCopy; ++i)
                {
                    ((Outlook._MailItem)oMsg).Send();
                    lo.writeLog(LogMessage: "Mail sent.", debugOnly: true);
                }
                // Clean up.
                oRecips = null;
                oMsg = null;
                oApp = null;
            }
            catch (Exception ex2)
            {
                lo.writeLog(LogMessage: "Failed to send the mail.", isError: true, Params: new List<string> { ex2.ToString(), this.ToJson() });
            }
        }


    } //end of sqMail()
}


